#include "timing.hpp"
#include "magic_enum.hpp"
#include "logger.hpp"
#include <iostream>
#include <iomanip>
#include <array>

namespace hms
{

template<typename Step, int nSteps>
void printTimings(
	const ArrayNs<nSteps>& t,
	std::string sumDescription,
	std::array<std::string, nSteps>&& stepDescriptions
){
	scalar sum { t.sum() };

	static constexpr int prec {3}, pad {2};
	fmt::memory_buffer out;
	fmt::format_to(std::back_inserter(out),
		"{0}: {1:.{2}f}s", sumDescription, sum, prec
	);
	for (Index i{0}; i<nSteps; ++i){
		if ( !stepDescriptions[i].empty() )
			fmt::format_to(std::back_inserter(out),
				"\n{0}{2}{1}{3}{1}for {4}",
				indent(),
				fmt::format("{:>{}}", "", pad),
				fmt::format( "{2:>{1}.{0}f}%",
					prec, indentSize + 3 + prec, 100 * t[i] / sum ),
				fmt::format( "{2:>{1}.{0}e}s",
					prec, 2 + prec + 4, t[i] ),
				stepDescriptions[i]
			);
	}
	log::getLogger()->info( "{}", fmt::to_string(out) );
}

template<typename Step, int nSteps>
void setTiming( ArrayNs<nSteps>& timings, Step step, Timer& t ){
	timings[static_cast<Index>(step)] += t.elapsed();
	t.reset();
}

} // namespace hms